﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Drawing;

namespace App1
{
    class GameChess
    {
        private static bool _marked = false;
        private static Pieces _pieceMark;
        private static int _winner = 0;
        private static PictureBox _picCheck = new PictureBox();
        private static PictureBox _picStalemate = new PictureBox();
        private static bool _onPlay = false;
        private static int _playing = 0;
        private static int _nTurn = 0;

        public static int nTurn
        {
            get { return GameChess._nTurn; }
            set { GameChess._nTurn = value; }
        }
        private static Move[] _logMove;

        private static Player[] _player = new Player[2];

        public static int Winner
        {
            get { return GameChess._winner; }
            set { GameChess._winner = value; }
        }
        
        public static PictureBox picCheck
        {
            get { return GameChess._picCheck; }
            set { GameChess._picCheck = value; }
        }
       
        public static PictureBox picStalemate
        {
            get { return GameChess._picStalemate; }
            set { GameChess._picStalemate = value; }
        }

        public static bool Marked
        {
            get { return GameChess._marked; }
            set { GameChess._marked = value; }
        }
        public static bool OnPlay
        {
            get { return GameChess._onPlay; }
            set { GameChess._onPlay = value; }
        }
        
        public static Pieces PieceMark
        {
            get { return GameChess._pieceMark; }
            set { GameChess._pieceMark = value; }
        }

        public static Player[] Player
        {
            get { return GameChess._player; }
            set { GameChess._player = value; }
        }

        static GameChess()
        {
            _player[0] = new Player(1);
            _player[1] = new Player(2);
        }

        public static void SaveToLogMove(Pieces piece)
        {
            _nTurn++;
            Array.Resize<Move>(ref _logMove, _nTurn);
            _logMove[_nTurn - 1] = new Move();
            _logMove[_nTurn - 1].Piece = _pieceMark;
            _logMove[_nTurn - 1].SquareCurr.Row = _pieceMark.Row;
            _logMove[_nTurn - 1].SquareCurr.Col = _pieceMark.Col;
            _logMove[_nTurn - 1].SquareNew.Row = piece.Row;
            _logMove[_nTurn - 1].SquareNew.Col = piece.Col;
        }

        public static void Undo()
        {
            if (!_marked && _nTurn > 0)
            {
                Pieces pieceTemp = new Pieces();
                Pieces pT = _logMove[_nTurn - 1].Piece;

                switch (_logMove[_nTurn -1].Piece.Value)
                {
                    case 1:
                        if (pT.Name == "Pawn0")
                            pieceTemp = _player[pT.Side - 1].Pawns[0];
                        else if (pT.Name== "Pawn1")
                            pieceTemp = _player[pT.Side - 1].Pawns[1];
                        else if (pT.Name == "Pawn2")
                            pieceTemp = _player[pT.Side - 1].Pawns[2];
                        else if (pT.Name == "Pawn3")
                            pieceTemp = _player[pT.Side - 1].Pawns[3];
                        else if (pT.Name == "Pawn4")
                            pieceTemp = _player[pT.Side - 1].Pawns[4];
                        break;
                    case 2:
                        if (pT.Name == "Guard0")
                            pieceTemp = _player[pT.Side - 1].Guards[0];
                        else if (pT.Name == "Guard1")
                            pieceTemp = _player[pT.Side - 1].Guards[1];
                        break;
                    case 3:
                        if (pT.Name == "Elephant0")
                            pieceTemp = _player[pT.Side - 1].Elephants[0];
                        else if (pT.Name == "Elephant1")
                            pieceTemp = _player[pT.Side - 1].Elephants[1];
                        break;
                    case 4:
                        if (pT.Name == "Horse0")
                            pieceTemp = _player[pT.Side - 1].Horses[0];
                        else if (pT.Name == "Horse1")
                            pieceTemp = _player[pT.Side - 1].Horses[1];
                        break;
                    case 5:
                        if (pT.Name == "Cannon0")
                            pieceTemp = _player[pT.Side - 1].Cannons[0];
                        else if (pT.Name == "Cannon1")
                            pieceTemp = _player[pT.Side - 1].Cannons[1];
                        break;
                    case 6:
                        if (pT.Name == "Rook0")
                            pieceTemp = _player[pT.Side - 1].Rooks[0];
                        else if (pT.Name == "Rook1")
                            pieceTemp = _player[pT.Side - 1].Rooks[1];
                        break;
                    case 7:
                        pieceTemp = _player[pT.Side - 1].King;
                        break;
                }

                MakeEmptySquare(pT.Row, pT.Col);
                SetPieceOnBoard(pieceTemp, _logMove[_nTurn - 1].SquareCurr.Row, _logMove[_nTurn - 1].SquareCurr.Col);

                if (_nTurn > 0)
                    --_nTurn;
                Array.Resize<Move>(ref _logMove, _nTurn);
                CheckCheck();
                ChangeTurn();
            }
        }

        public static void KillPiece(Pieces piece)
        {
            piece.State = false;
            piece.pic.Visible = false;
        }

        public static void MakeEmptySquare(int row, int col)
        {
            Board.Init(row, col, "", 0, 3, false);
        }

        public static void SetPieceOnBoard(Pieces piece, int row, int col)
        {
            Board.Init(row, col, piece.Name, piece.Value, piece.Side, true);
            piece.Row = row;
            piece.Col = col;
            piece.pic.Top = row * 63;
            piece.pic.Left = col * 63;
        }

        private static int Check()
        {
            int row = _player[1].King.Row;
            int col = _player[1].King.Col;
            if (_player[0].Pawns[0].State
                && _player[0].Pawns[0].CheckLegalMove(row, col))
                return 1;

            if (_player[0].Pawns[1].State
                && _player[0].Pawns[1].CheckLegalMove(row, col))
                return 1;

            if (_player[0].Pawns[2].State 
                && _player[0].Pawns[2].CheckLegalMove(row, col))                
                return 1;

            if (_player[0].Pawns[3].State 
                && _player[0].Pawns[3].CheckLegalMove(row, col))                
                return 1;

            if (_player[0].Pawns[4].State 
                && _player[0].Pawns[4].CheckLegalMove(row, col))               
                return 1;

            if (_player[0].Guards[0].State 
                && _player[0].Guards[0].CheckLegalMove(row, col))                
                return 1;

            if (_player[0].Guards[1].State 
                && _player[0].Guards[1].CheckLegalMove(row, col)) 
                return 1;

            if (_player[0].Elephants[0].State 
                && _player[0].Elephants[0].CheckLegalMove(row, col)) 
                return 1;

            if (_player[0].Elephants[1].State 
                && _player[0].Elephants[1].CheckLegalMove(row, col)) 
                return 1;

            if (_player[0].Horses[0].State 
                && _player[0].Horses[0].CheckLegalMove(row, col)) 
                return 1;

            if (_player[0].Horses[1].State 
                && _player[0].Horses[1].CheckLegalMove(row, col)) 
                return 1;

            if (_player[0].Cannons[0].State 
                && _player[0].Cannons[0].CheckLegalMove(row, col)) 
                return 1;

            if (_player[0].Cannons[1].State 
                && _player[0].Cannons[1].CheckLegalMove(row, col)) 
                return 1;

            if (_player[0].Rooks[0].State 
                && _player[0].Rooks[0].CheckLegalMove(row, col)) 
                return 1;
            if (_player[0].Rooks[1].State 
                && _player[0].Rooks[1].CheckLegalMove(row, col)) 
                return 1;

            row = _player[0].King.Row;
            col = _player[0].King.Col;
            if (_player[1].Pawns[0].State 
                && _player[1].Pawns[0].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Pawns[1].State 
                && _player[1].Pawns[1].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Pawns[2].State 
                && _player[1].Pawns[2].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Pawns[3].State 
                && _player[1].Pawns[3].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Pawns[4].State 
                && _player[1].Pawns[4].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Guards[0].State 
                && _player[1].Guards[0].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Guards[1].State 
                && _player[1].Guards[1].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Elephants[0].State 
                && _player[1].Elephants[0].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Elephants[1].State 
                && _player[1].Elephants[1].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Horses[0].State 
                && _player[1].Horses[0].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Horses[1].State 
                && _player[1].Horses[1].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Cannons[0].State 
                && _player[1].Cannons[0].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Cannons[1].State 
                && _player[1].Cannons[1].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Rooks[0].State 
                && _player[1].Rooks[0].CheckLegalMove(row, col)) 
                return 0;

            if (_player[1].Rooks[1].State 
                && _player[1].Rooks[1].CheckLegalMove(row, col)) 
                return 0;
            return 2;
        }

        public static void CheckCheck()
        {
            int check = Check();
            if (check == 0)
            {
                //MessageBox.Show("Chieu!");
                _player[0].King.pic.Image = Properties.Resources.aKingCheck;
                _player[1].King.pic.Image = Properties.Resources.bKing;
            }
            else
                if (check == 1)
                {
                    _player[1].King.pic.Image = Properties.Resources.bKingCheck;
                    _player[0].King.pic.Image = Properties.Resources.aKing;
                }
                else
                {
                    _player[0].King.pic.Image = Properties.Resources.aKing;
                    _player[1].King.pic.Image = Properties.Resources.bKing;
                }
        }

        public static void ChangeTurn()
        {
            _playing = 1 - _playing;

            _player[_playing].Pawns[0].Lock = false;
            _player[_playing].Pawns[1].Lock = false;
            _player[_playing].Pawns[2].Lock = false;
            _player[_playing].Pawns[3].Lock = false;
            _player[_playing].Pawns[4].Lock = false;
            _player[_playing].Guards[0].Lock = false;
            _player[_playing].Guards[1].Lock = false;
            _player[_playing].Elephants[0].Lock = false;
            _player[_playing].Elephants[1].Lock = false;
            _player[_playing].Horses[0].Lock = false;
            _player[_playing].Horses[1].Lock = false;
            _player[_playing].Cannons[0].Lock = false;
            _player[_playing].Cannons[1].Lock = false;
            _player[_playing].Rooks[0].Lock = false;
            _player[_playing].Rooks[1].Lock = false;
            _player[_playing].King.Lock = false;

            _player[1-_playing].Pawns[0].Lock = true;
            _player[1-_playing].Pawns[1].Lock = true;
            _player[1-_playing].Pawns[2].Lock = true;
            _player[1-_playing].Pawns[3].Lock = true;
            _player[1-_playing].Pawns[4].Lock = true;
            _player[1-_playing].Guards[0].Lock = true;
            _player[1-_playing].Guards[1].Lock = true;
            _player[1-_playing].Elephants[0].Lock = true;
            _player[1-_playing].Elephants[1].Lock = true;
            _player[1-_playing].Horses[0].Lock = true;
            _player[1-_playing].Horses[1].Lock = true;
            _player[1-_playing].Cannons[0].Lock = true;
            _player[1-_playing].Cannons[1].Lock = true;
            _player[1-_playing].Rooks[0].Lock = true;
            _player[1-_playing].Rooks[1].Lock = true;
            _player[1-_playing].King.Lock = true;
        }

        public static void CheckStalemate()
        { 
        }

        public static void NewGame()
        {
            //_player[0] = new Player(1);
            //_player[1] = new Player(2);
            if (_onPlay)
            {
                int i = 0;
                while (i < 2)
                {
                    _player[i].Pawns[0].pic.Visible = false;
                    _player[i].Pawns[1].pic.Visible = false;
                    _player[i].Pawns[2].pic.Visible = false;
                    _player[i].Pawns[3].pic.Visible = false;
                    _player[i].Pawns[4].pic.Visible = false;
                    
                    _player[i].Guards[0].pic.Visible = false;
                    _player[i].Guards[1].pic.Visible = false;
                    
                    _player[i].Elephants[0].pic.Visible = false;
                    _player[i].Elephants[1].pic.Visible = false;
                    
                    _player[i].Horses[0].pic.Visible = false;
                    _player[i].Horses[1].pic.Visible = false;
                    
                    _player[i].Cannons[0].pic.Visible = false;
                    _player[i].Cannons[1].pic.Visible = false;
                    
                    _player[i].Rooks[0].pic.Visible = false;
                    _player[i].Rooks[1].pic.Visible = false;
                    
                    _player[i].King.pic.Visible = false;
                    ++i;
                }
                Array.Resize<Player>(ref _player, 0);

                Array.Resize<Player>(ref _player, 2);
                _player[0] = new Player(1);
                _player[1] = new Player(2);

                Board.ResetBoard();
                _playing = 0;
                _winner = 0;

                i = 0;
                while (i < 2)
                {
                    _player[i].Pawns[0].SetImage();
                    _player[i].Pawns[1].SetImage();
                    _player[i].Pawns[2].SetImage();
                    _player[i].Pawns[3].SetImage();
                    _player[i].Pawns[4].SetImage();
                    
                    _player[i].Guards[0].SetImage();
                    _player[i].Guards[1].SetImage();
                    
                    _player[i].Elephants[0].SetImage();
                    _player[i].Elephants[1].SetImage();
                    
                    _player[i].Horses[0].SetImage();
                    _player[i].Horses[1].SetImage();
                    
                    _player[i].Cannons[0].SetImage();
                    _player[i].Cannons[1].SetImage();
                    
                    _player[i].Rooks[0].SetImage();
                    _player[i].Rooks[1].SetImage();
                    
                    _player[i].King.SetImage();
                    ++i;
                }
            }
            else
            {
                Board.ResetBoard();
                _onPlay = true;

                int i = 0;
                while (i < 2)
                {
                    _player[i].Pawns[0].SetImage();
                    _player[i].Pawns[1].SetImage();
                    _player[i].Pawns[2].SetImage();
                    _player[i].Pawns[3].SetImage();
                    _player[i].Pawns[4].SetImage();
                    _player[i].Guards[0].SetImage();
                    _player[i].Guards[1].SetImage();
                    _player[i].Elephants[0].SetImage();
                    _player[i].Elephants[1].SetImage();
                    _player[i].Horses[0].SetImage();
                    _player[i].Horses[1].SetImage();
                    _player[i].Cannons[0].SetImage();
                    _player[i].Cannons[1].SetImage();
                    _player[i].Rooks[0].SetImage();
                    _player[i].Rooks[1].SetImage();
                    _player[i].King.SetImage();
                    ++i;
                }
            }
        }

        public static void OpenGame()
        {
           // _player[0] = new Player(1);
           // _player[1] = new Player(2);
            if (_onPlay)
            {
                int i = 0;
                while (i < 2)
                {
                    _player[i].Pawns[0].pic.Visible = false;
                    _player[i].Pawns[1].pic.Visible = false;
                    _player[i].Pawns[2].pic.Visible = false;
                    _player[i].Pawns[3].pic.Visible = false;
                    _player[i].Pawns[4].pic.Visible = false;

                    _player[i].Guards[0].pic.Visible = false;
                    _player[i].Guards[1].pic.Visible = false;

                    _player[i].Elephants[0].pic.Visible = false;
                    _player[i].Elephants[1].pic.Visible = false;

                    _player[i].Horses[0].pic.Visible = false;
                    _player[i].Horses[1].pic.Visible = false;

                    _player[i].Cannons[0].pic.Visible = false;
                    _player[i].Cannons[1].pic.Visible = false;

                    _player[i].Rooks[0].pic.Visible = false;
                    _player[i].Rooks[1].pic.Visible = false;

                    _player[i].King.pic.Visible = false;
                    ++i;
                }
                Array.Resize<Player>(ref _player, 0);

                Array.Resize<Player>(ref _player, 2);
                _player[0] = new Player(1);
                _player[1] = new Player(2);
            }
        }

        public static void UdateOpen()
        {

            Board.ResetBoard();
            _onPlay = true;

            int i = 0;
            while (i < 2)
            {
                _player[i].Pawns[0].Init(_player[i].Pawns[0].Row, _player[i].Pawns[0].Col, "Pawn0", 1, i + 1, _player[i].Pawns[0].State, false);
                _player[i].Pawns[0].SetImage();
                _player[i].Pawns[1].Init(_player[i].Pawns[1].Row, _player[i].Pawns[1].Col, "Pawn1", 1, i + 1, _player[i].Pawns[1].State, false);
                _player[i].Pawns[1].SetImage();
                _player[i].Pawns[2].Init(_player[i].Pawns[2].Row, _player[i].Pawns[2].Col, "Pawn2", 1, i + 1, _player[i].Pawns[2].State, false);
                _player[i].Pawns[2].SetImage();
                _player[i].Pawns[3].Init(_player[i].Pawns[3].Row, _player[i].Pawns[3].Col, "Pawn3", 1, i + 1, _player[i].Pawns[3].State, false);
                _player[i].Pawns[3].SetImage();
                _player[i].Pawns[4].Init(_player[i].Pawns[4].Row, _player[i].Pawns[4].Col, "Pawn4", 1, i + 1, _player[i].Pawns[4].State, false);
                _player[i].Pawns[4].SetImage();
                _player[i].Guards[0].Init(_player[i].Guards[0].Row, _player[i].Guards[0].Col, "Guard0", 2, i + 1, _player[i].Guards[0].State, false);
                _player[i].Guards[0].SetImage();
                _player[i].Guards[1].Init(_player[i].Guards[1].Row, _player[i].Guards[1].Col, "Guard1", 2, i + 1, _player[i].Guards[1].State, false);
                _player[i].Guards[1].SetImage();
                _player[i].Elephants[0].Init(_player[i].Elephants[0].Row, _player[i].Elephants[0].Col, "Elephant0", 3, i + 1, _player[i].Elephants[0].State, false);
                _player[i].Elephants[0].SetImage();
                _player[i].Elephants[1].Init(_player[i].Elephants[1].Row, _player[i].Elephants[1].Col, "Elephant1", 3, i + 1, _player[i].Elephants[1].State, false);
                _player[i].Elephants[1].SetImage();
                _player[i].Horses[0].Init(_player[i].Horses[0].Row, _player[i].Horses[0].Col, "Horse0", 4, i + 1, _player[i].Horses[0].State, false);
                _player[i].Horses[0].SetImage();
                _player[i].Horses[1].Init(_player[i].Horses[1].Row, _player[i].Horses[1].Col, "Horse1", 4, i + 1, _player[i].Horses[1].State, false);
                _player[i].Horses[1].SetImage();
                _player[i].Cannons[0].Init(_player[i].Cannons[0].Row, _player[i].Cannons[0].Col, "Cannon0", 5, i + 1, _player[i].Cannons[0].State, false);
                _player[i].Cannons[0].SetImage();
                _player[i].Cannons[1].Init(_player[i].Cannons[1].Row, _player[i].Cannons[1].Col, "Cannon1", 5, i + 1, _player[i].Cannons[1].State, false);
                _player[i].Cannons[1].SetImage();
                _player[i].Rooks[0].Init(_player[i].Rooks[0].Row, _player[i].Rooks[0].Col, "Rook0", 6, i + 1, _player[i].Rooks[0].State, false);
                _player[i].Rooks[0].SetImage();
                _player[i].Rooks[1].Init(_player[i].Rooks[1].Row, _player[i].Rooks[1].Col, "Rook1", 6, i + 1, _player[i].Rooks[1].State, false);
                _player[i].Rooks[1].SetImage();
                _player[i].King.Init(_player[i].King.Row, _player[i].King.Col, "King", 7, i + 1, _player[i].King.State, false);
                _player[i].King.SetImage();
                ++i;
         
            }
        }

        public static void Set_Playing(int temp)
        {
            _playing = temp;
        }
    }
}
